﻿using System;
using System.Collections.Generic;
using System.IO;

namespace ServerFramework.Tools
{
    /// <summary>
    /// configuration class use for read txt file,
    /// text like :
    /// 
    /// [Section1]  
    /// KeyWord1 = Value1  
    /// KeyWord2 = Value2  
    /// ...  
    /// [Section2]  
    /// KeyWord3 = Value3  
    /// KeyWord4 = Value4 
    /// </summary>

    public class Configuration
    {
        #region class config section
        /// <summary>
        /// config section class
        /// </summary>
        protected class ConfigSection
        {
            private SortedDictionary<string, string> m_section = new SortedDictionary<string, string>();

            /// <summary>
            /// add key and val
            /// </summary>
            public bool AddKeyVal(string key, string val)
            {
                if (m_section.ContainsKey(key))
                {
                    return false;
                }
                m_section.Add(key, val);
                return true;
            }

            /// <summary>
            /// get val by key
            /// </summary>
            public string GetValByKey(string key)
            {
                if (m_section.ContainsKey(key))
                {
                    return m_section[key];
                }
                return null;
            }
        }
        #endregion


        private SortedDictionary<string, ConfigSection> m_config = new SortedDictionary<string, ConfigSection>();

        private StreamReader m_streamReader = null;

        private ConfigSection m_tempSection = null;


        public List<int> GetIntListFromString(string sour, char seg)
        {
            List<int> list = new List<int>();
            string[] temp = sour.Split(seg);
            foreach (string s in temp)
            {
                list.Add(int.Parse(s));
            }
            return list;

        }

        /// <summary>
        /// load config by file name
        /// </summary>
        public bool LoadConfig(string fileName)
        {
            try
            {
                m_streamReader = new StreamReader(fileName);
            }
            catch (Exception e)
            {
                Log.WriteLog(ELogLevel.LOG_ERROR, e.Message + " confg name:" + fileName);
                return false;
            }

            bool readRet = ReadFile();
            m_streamReader.Close();
            return readRet;
        }


        /// <summary>
        /// load config by file stream
        /// </summary>
        public bool LoadConfig(byte[] fileStream)
        {
            if (fileStream == null)
            {
                return false;
            }
            MemoryStream stream = new MemoryStream(fileStream);
            m_streamReader = new StreamReader(stream);
            bool readRet = ReadFile();
            m_streamReader.Close();
            stream.Close();
            return readRet;
        }

        /// <summary>
        /// get val by section and key ,if not find ,return null
        /// </summary>
        public string GetVal(string section, string key)
        {
            if (m_config.ContainsKey(section))
            {
                m_tempSection = m_config[section];
                return m_tempSection.GetValByKey(key);
            }
            return null;
        }


        /// <summary>
        /// read config file ,if format error  return false
        /// </summary>
        private bool ReadFile()
        {
            {
                while (!m_streamReader.EndOfStream)
                {
                    string line = m_streamReader.ReadLine();

                    //remove annotation
                    int startAnnotationIndex = line.IndexOf("--");
                    if (startAnnotationIndex >= 0 && startAnnotationIndex < line.Length)
                    {
                        line = line.Remove(startAnnotationIndex, line.Length - startAnnotationIndex);
                    }

                    line = line.Trim(' ', '\r', '\n');
                    line = line.Replace(" ", "");
                    line = line.Replace("\t", "");
                    if (line.Contains("[") && line.Contains("]"))
                    {
                        line = line.Trim('[', ']');
                        m_tempSection = new ConfigSection();
                        m_config.Add(line, m_tempSection);
                    }
                    else if (line.Contains("="))
                    {
                        string[] keyVal = line.Split('=');
                        if (keyVal.Length == 2)
                        {
                            m_tempSection.AddKeyVal(keyVal[0], keyVal[1]);
                        }
                        else
                        {
                            return false;
                        }
                    }
                }
                return true;

            }

        }
    }
}
